.text
.global task_switch
.extern current_task

# void task_switch(void* next);
# 
# 参数:
#   %rdi - 指向下一个任务的TCB指针
#
# 注意: 在x86-64 System V ABI中:
# - 调用者保存寄存器: %rax, %rcx, %rdx, %rsi, %rdi, %r8-r11
# - 被调用者保存寄存器: %rbx, %rbp, %r12-r15
#
# 我们只需要保存被调用者保存寄存器

task_switch:
    # 获取当前任务的TCB指针
    movq current_task(%rip), %rax
    
    # 检查current_task是否为NULL
    testq %rax, %rax
    jz skip_save  # 如果为空，跳过保存当前上下文
    
    # 保存当前上下文到当前任务的栈上
    pushq %rbp
    pushq %rbx
    pushq %r12
    pushq %r13
    pushq %r14
    pushq %r15
    
    # 保存当前栈指针到当前任务的TCB中
    movq %rsp, (%rax)
    
skip_save:
    # 切换到新任务
    movq %rdi, current_task(%rip)  #rdi是第一个参数，也就是下一个任务的TCB指针
    
    # 加载新任务的栈指针
    movq (%rdi), %rsp
    
    # 恢复新任务的上下文
    popq %r15
    popq %r14
    popq %r13
    popq %r12
    popq %rbx
    popq %rbp
    
    # 返回到新任务
    ret
